/*
 * Copyright 2012 ZXing authors
 *
 * Licensed under the Apache License, Version 2.0 (the "License");
 * you may not use this file except in compliance with the License.
 * You may obtain a copy of the License at
 *
 *      http://www.apache.org/licenses/LICENSE-2.0
 *
 * Unless required by applicable law or agreed to in writing, software
 * distributed under the License is distributed on an "AS IS" BASIS,
 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
 * See the License for the specific language governing permissions and
 * limitations under the License.
 */

#import <AudioToolbox/AudioToolbox.h>
#import "ScanCodeViewController.h"

#import "ScanCodeQRView.h"
#import "RKTabView.h"

#import <CTAssetsPickerController/CTAssetsPickerController.h>
#import <CTAssetsPickerController/CTAssetsPageViewController.h>
#import <CTAssetsPickerController/CTAssetsPickerController.h>
#import <CTAssetsPickerController/CTAssetsPageViewController.h>
#import <CTAssetsPickerController/CTAssetCollectionViewCell.h>
#import <CTAssetsPickerController/CTAssetsGridView.h>
#import <CTAssetsPickerController/CTAssetsGridViewFooter.h>
#import <CTAssetsPickerController/CTAssetsGridViewCell.h>
#import <CTAssetsPickerController/CTAssetsGridSelectedView.h>
#import <CTAssetsPickerController/CTAssetCheckmark.h>
#import <CTAssetsPickerController/CTAssetSelectionLabel.h>
#import <CTAssetsPickerController/CTAssetsPageView.h>

@interface ScanCodeViewController ()<RKTabViewDelegate,CTAssetsPickerControllerDelegate>

@property (nonatomic, strong) ZXCapture *capture;
@property (nonatomic, weak) IBOutlet UIView *scanRectView;
@property (nonatomic, weak) IBOutlet UIView *scanBoxView;
@property (nonatomic, weak) IBOutlet UILabel *decodedLabel;

@property (nonatomic, strong) IBOutlet RKTabView *titledTabsView;
@property (nonatomic, strong) AVCaptureDevice *device;

@property (nonatomic, assign) BarcodeType barcodeType;

@end

@implementation ScanCodeViewController

- (void)dealloc
{
    [self.capture hard_stop];
    [self.capture.layer removeFromSuperlayer];
    [self closeFlashlight];
}

- (void)viewDidLoad
{
    [super viewDidLoad];

    self.capture = [[ZXCapture alloc] init];
    self.capture.camera = self.capture.back;
    self.capture.focusMode = AVCaptureFocusModeContinuousAutoFocus;
    self.capture.rotation = 90.0f;
    self.capture.delegate = self;

    self.capture.layer.frame = self.view.bounds;
    [self.view.layer addSublayer:self.capture.layer];

    [self.view bringSubviewToFront:self.scanRectView];
    [self.view bringSubviewToFront:self.decodedLabel];
    
    //扫描框
    CGRect screenRect = [UIScreen mainScreen].bounds;
    ScanCodeQRView *qrRectView = [[ScanCodeQRView alloc] initWithFrame:screenRect];
    qrRectView.transparentArea = CGSizeMake(260*screenRect.size.width/320, 280*screenRect.size.height/480);
    qrRectView.backgroundColor = [UIColor clearColor];
    qrRectView.center = CGPointMake(screenRect.size.width / 2, screenRect.size.height / 2);
    //qrRectView.delegate = self;
    [self.scanBoxView addSubview:qrRectView];
    
    //选项卡
    UIColor *color = [UIColor colorWithRed:159/255.0 green:159/255.0 blue:159/255.0 alpha:1.0];
    RKTabItem *mastercardTabItem = [RKTabItem createUsualItemWithImageEnabled:[UIImage imageNamed:@"icon_qrcord_hover"] imageDisabled:[UIImage imageNamed:@"icon_qrcord_normal"]];
    mastercardTabItem.titleString = @"二维码";
    mastercardTabItem.titleFont = [UIFont systemFontOfSize:11];
    [mastercardTabItem titleFontColorEnabled:ThemeColorBlue titleFontColorDisabled:color];
    
    RKTabItem *paypalTabItem = [RKTabItem createUsualItemWithImageEnabled:[UIImage imageNamed:@"icon_-barcode_hover"] imageDisabled:[UIImage imageNamed:@"icon_-barcode_normal"]];
    paypalTabItem.titleString = @"条形码";
    paypalTabItem.titleFont = [UIFont systemFontOfSize:11];
    [paypalTabItem titleFontColorEnabled:ThemeColorBlue titleFontColorDisabled:color];
    mastercardTabItem.tabState = TabStateEnabled;
    
    self.titledTabsView.darkensBackgroundForEnabledTabs = YES;
    self.titledTabsView.tabItems = @[mastercardTabItem, paypalTabItem];
    self.titledTabsView.delegate = self;
}

- (void)viewWillDisappear:(BOOL)animated
{
//    [super viewWillDisappear:animated];
    
//    [self.navigationController setNavigationBarHidden:NO animated:NO];
//    [[UIApplication sharedApplication] setStatusBarHidden:NO withAnimation:UIStatusBarAnimationNone];
}

- (void)viewWillAppear:(BOOL)animated
{
    [super viewWillAppear:animated];
    
    [self.navigationController setNavigationBarHidden:YES animated:YES];
//    [[UIApplication sharedApplication] setStatusBarHidden:YES withAnimation:UIStatusBarAnimationNone];
    
    self.capture.delegate = self;
    self.capture.layer.frame = [UIScreen mainScreen].bounds;

    CGAffineTransform captureSizeTransform = CGAffineTransformMakeScale(SuperWidth / self.view.frame.size.width, SuperHeight / self.view.frame.size.height);
    self.capture.scanRect = CGRectApplyAffineTransform(self.scanRectView.frame, captureSizeTransform);
}

#pragma mark - View Controller Methods

- (IBAction)backSelector:(id)sender
{
    [self backButtonEvent:sender];
}

- (IBAction)imageGainSelector:(id)sender
{
    //设置照片选择样式
    [self setCTApperanceViewControllerStyle];
    
    [PHPhotoLibrary requestAuthorization:^(PHAuthorizationStatus status){
        dispatch_async(dispatch_get_main_queue(), ^{
            
            // init picker
            CTAssetsPickerController *picker = [[CTAssetsPickerController alloc] init];
            
            // set delegate
            picker.delegate = self;
            
            // Optionally present picker as a form sheet on iPad
            if (UI_USER_INTERFACE_IDIOM() == UIUserInterfaceIdiomPad)
            picker.modalPresentationStyle = UIModalPresentationFormSheet;
            
            // present picker
            [self presentViewController:picker animated:YES completion:nil];
        });
    }];
    
}

//设置照片选择样式
- (void)setCTApperanceViewControllerStyle
{
    UIColor *color1 = ThemeColorBlue;
    UIColor *color2 = [UIColor whiteColor];
    UIColor *color3 = [UIColor whiteColor];
    UIFont  *font   = [UIFont boldSystemFontOfSize:18];
    
    // Navigation Bar apperance
    UINavigationBar *navBar = [UINavigationBar appearanceWhenContainedIn:[CTAssetsPickerController class], nil];
    
    // set nav bar style to black to force light content status bar style
    navBar.barStyle = UIBarStyleBlack;
    
    // bar tint color
    navBar.barTintColor = color1;
    
    // tint color
    navBar.tintColor = color2;
    
    // title
    navBar.titleTextAttributes =
    @{NSForegroundColorAttributeName: color2,
      NSFontAttributeName : font};
    
    // bar button item appearance
    UIBarButtonItem *barButtonItem = [UIBarButtonItem appearanceWhenContainedIn:[CTAssetsPickerController class], nil];
    [barButtonItem setTitleTextAttributes:@{NSFontAttributeName : [UIFont systemFontOfSize:17]}
                                 forState:UIControlStateNormal];
    
    // albums view
    UITableView *assetCollectionView = [UITableView appearanceWhenContainedIn:[CTAssetsPickerController class], nil];
    assetCollectionView.backgroundColor = color2;
    
    // asset collection appearance
//    CTAssetCollectionViewCell *assetCollectionViewCell = [CTAssetCollectionViewCell appearance];
//    assetCollectionViewCell.titleFont = [font fontWithSize:16.0];
//    assetCollectionViewCell.titleTextColor = color1;
//    assetCollectionViewCell.selectedTitleTextColor = color2;
//    assetCollectionViewCell.countFont = [font fontWithSize:12.0];
//    assetCollectionViewCell.countTextColor = color1;
//    assetCollectionViewCell.selectedCountTextColor = color2;
//    assetCollectionViewCell.accessoryColor = color1;
//    assetCollectionViewCell.selectedAccessoryColor = color2;
//    assetCollectionViewCell.backgroundColor = color3;
//    assetCollectionViewCell.selectedBackgroundColor = [color1 colorWithAlphaComponent:0.4];
    
    // grid view
    CTAssetsGridView *assetsGridView = [CTAssetsGridView appearance];
    assetsGridView.gridBackgroundColor = color3;
    
    // assets grid footer apperance
    CTAssetsGridViewFooter *assetsGridViewFooter = [CTAssetsGridViewFooter appearance];
    assetsGridViewFooter.font = [font fontWithSize:16.0];
    assetsGridViewFooter.textColor = color2;
    
    // grid view cell
    CTAssetsGridViewCell *assetsGridViewCell = [CTAssetsGridViewCell appearance];
    assetsGridViewCell.highlightedColor = [UIColor colorWithWhite:1 alpha:0.3];
    
    // selected grid view
    CTAssetsGridSelectedView *assetsGridSelectedView = [CTAssetsGridSelectedView appearance];
    assetsGridSelectedView.selectedBackgroundColor = [UIColor colorWithWhite:0 alpha:0.5];
    assetsGridSelectedView.tintColor = color1;
    assetsGridSelectedView.borderWidth = 3.0;
    
    // check mark
    CTAssetCheckmark *checkmark = [CTAssetCheckmark appearance];
    checkmark.tintColor = color1;
    [checkmark setMargin:0.0 forVerticalEdge:NSLayoutAttributeRight horizontalEdge:NSLayoutAttributeTop];
    
    // selection label
    CTAssetSelectionLabel *assetSelectionLabel = [CTAssetSelectionLabel appearance];
    assetSelectionLabel.borderWidth = 1.0;
    assetSelectionLabel.borderColor = color3;
    [assetSelectionLabel setSize:CGSizeMake(24.0, 24.0)];
    [assetSelectionLabel setCornerRadius:12.0];
    [assetSelectionLabel setMargin:4.0 forVerticalEdge:NSLayoutAttributeRight horizontalEdge:NSLayoutAttributeTop];
    [assetSelectionLabel setTextAttributes:@{NSFontAttributeName : [font fontWithSize:12.0],
                                             NSForegroundColorAttributeName : color3,
                                             NSBackgroundColorAttributeName : color1}];
    
    // page view (preview)
    CTAssetsPageView *assetsPageView = [CTAssetsPageView appearance];
    assetsPageView.pageBackgroundColor = color3;
    assetsPageView.fullscreenBackgroundColor = color2;
    
    // progress view
    [UIProgressView appearanceWhenContainedIn:[CTAssetsPickerController class], nil].tintColor = color1;
}

- (IBAction)openFlashlightSelector:(id)sender
{
    if(self.device){
        [self closeFlashlight];//关闭闪光灯
    }else {
        [self openFlashlight];//开启闪光灯
    }
}

#pragma 打开闪光灯

-(void)openFlashlight
{
    //AVCaptureDevice代表抽象的硬件设备
    AVCaptureDevice *device = [AVCaptureDevice defaultDeviceWithMediaType:AVMediaTypeVideo];
    if (![device hasTorch]) {//判断是否有闪光灯
        UIAlertView *alter = [[UIAlertView alloc]initWithTitle:@"温馨提示" message:@"当前设备没有闪光灯，不能提供手电筒功能" delegate:nil cancelButtonTitle:@"确定" otherButtonTitles:nil, nil];
        [alter show];
        return;
    } else {
        [device lockForConfiguration:nil];
        [device setTorchMode:AVCaptureTorchModeOn];
        [device unlockForConfiguration];
    }
    [self setDevice:device];
}

#pragma 关闭闪光灯

-(void)closeFlashlight
{
    if(self.device){//判断闪光灯是否打开
        [self.device lockForConfiguration:nil];
        [self.device setTorchMode: AVCaptureTorchModeOff];
        [self.device unlockForConfiguration];
        self.device = nil;
    }
}

#pragma mark - Private Methods

//条码类型判断
- (BarcodeType)barcodeTypeVerification:(ZXBarcodeFormat)barcodeFormat
{
    switch (barcodeFormat) {
        case kBarcodeFormatAztec://二维码
            return BarcodeTypeQRcode;
            
        case kBarcodeFormatCodabar://一维码
            return BarcodeTypeBarcode;
            
        case kBarcodeFormatCode39://一维码
            return BarcodeTypeBarcode;
            
        case kBarcodeFormatCode93: //一维码
            return BarcodeTypeBarcode;
            
        case kBarcodeFormatCode128://一维码
            return BarcodeTypeBarcode;
            
        case kBarcodeFormatDataMatrix: //二维码
            return BarcodeTypeQRcode;
            
        case kBarcodeFormatEan8://一维码
            return BarcodeTypeBarcode;
            
        case kBarcodeFormatEan13://一维码
            return BarcodeTypeBarcode;
            
        case kBarcodeFormatITF://一维码
            return BarcodeTypeBarcode;
            
        case kBarcodeFormatPDF417://一维码
            return BarcodeTypeBarcode;
            
        case kBarcodeFormatQRCode: //二维码
            return BarcodeTypeQRcode;
            
        case kBarcodeFormatRSS14://一维码
            return BarcodeTypeBarcode;
            
        case kBarcodeFormatRSSExpanded://一维码
            return BarcodeTypeBarcode;
            
        case kBarcodeFormatUPCA://一维码
            return BarcodeTypeBarcode;
            
        case kBarcodeFormatUPCE://一维码
            return BarcodeTypeBarcode;
            
        case kBarcodeFormatUPCEANExtension://独立
            return BarcodeTypeOther;
            
        case kBarcodeFormatMaxiCode: //二维码
            return BarcodeTypeQRcode;
            
        default:
            return BarcodeTypeOther;
    }
}

#pragma mark - ZXCaptureDelegate Methods

- (void)captureResult:(ZXCapture *)capture result:(ZXResult *)result
{
    if (!result) return;
    if ([self barcodeTypeVerification:result.barcodeFormat] != self.barcodeType) return;

    // We got a result. Display information about the result onscreen.
    //NSString *formatString = [self barcodeFormatToString:result.barcodeFormat];
    NSString *display = [NSString stringWithFormat:@"扫描成功!"];
    [self.decodedLabel performSelectorOnMainThread:@selector(setText:) withObject:display waitUntilDone:YES];

    // Vibrate and Video
    AudioServicesPlaySystemSound(kSystemSoundID_Vibrate);
    AudioServicesPlaySystemSound(1110);
    [self.capture stop];
    
    //关闭窗体
    [self.navigationController popViewControllerAnimated:YES];
    if (self.backResultDelagate && [self.backResultDelagate respondsToSelector:@selector(backResultDataKey:dataValue:)])
        [self.backResultDelagate backResultDataKey:self.key dataValue:result];
}

#pragma mark - RKTabViewDelegate

- (void)tabView:(RKTabView *)tabView tabBecameEnabledAtIndex:(int)index tab:(RKTabItem *)tabItem
{
    NSLog(@"Tab Bar %tu became enabled on tab view", index);
    if (index == 0) {//扫描二维码
        self.barcodeType = BarcodeTypeQRcode;
        self.decodedLabel.text = @"将二维码放入扫描框内，即可自动扫描";
        
    } else if (index == 1){ //扫描条形码
        self.barcodeType = BarcodeTypeBarcode;
        self.decodedLabel.text = @"将条形码放入扫描框内，即可自动扫描";
    }
}

- (void)tabView:(RKTabView *)tabView tabBecameDisabledAtIndex:(int)index tab:(RKTabItem *)tabItem
{
    NSLog(@"Tab № %tu became disabled on tab view", index);
}

#pragma mark -
#pragma mark - Assets Picker Delegate

- (void)assetsPickerController:(CTAssetsPickerController *)picker didFinishPickingAssets:(NSArray *)assets
{
    if (assets.count<=0) {
        NSString *message = [NSString stringWithFormat:@"您没有选择照片"];
        UIAlertView *alert=[[UIAlertView alloc] initWithTitle:@"温馨提示" message:message delegate:nil
                                            cancelButtonTitle:@"确定" otherButtonTitles:nil];
        [alert show];
        return;
    }
    
    //遍历照片和视频
    for (PHAsset *dataAsset in assets) {
        if (dataAsset.mediaType == PHAssetMediaTypeImage) {//照片类型
            PHImageManager * imageManager = [PHImageManager defaultManager];
            [imageManager requestImageDataForAsset:dataAsset options:nil resultHandler:^(NSData * _Nullable imageData, NSString * _Nullable dataUTI, UIImageOrientation orientation, NSDictionary * _Nullable info) {
                UIImage *image = [UIImage imageWithData:imageData];
                CGImageRef ratioThum = image.CGImage;
                
                //获取等比图片
                ZXLuminanceSource* source = [[ZXCGImageLuminanceSource alloc] initWithCGImage:ratioThum] ;
                ZXBinaryBitmap* bitmap = [ZXBinaryBitmap binaryBitmapWithBinarizer:[ZXHybridBinarizer binarizerWithSource:source]];
                
                NSError* error = nil;
                ZXDecodeHints* hints = [ZXDecodeHints hints];
                hints.encoding = NSUTF8StringEncoding;
                
                ZXMultiFormatReader* reader = [ZXMultiFormatReader reader];
                ZXResult* result = [reader decode:bitmap hints:nil error:&error];
                
                if (result) {
                    [self captureResult:self.capture result:result];
                } else {
                    NSString *message = [NSString stringWithFormat:@"没有识别到条码信息，请选择有条码的照片"];
                    UIAlertView *alert=[[UIAlertView alloc] initWithTitle:@"温馨提示" message:message delegate:nil
                                                        cancelButtonTitle:@"确定" otherButtonTitles:nil];
                    [alert show];
                }
                [picker dismissViewControllerAnimated:YES completion:nil];
                
            }];
            
        } else if (dataAsset.mediaType == PHAssetMediaTypeVideo) {//视频类型
            NSString *message = [NSString stringWithFormat:@"不能识别视频，请重新选择"];
            UIAlertView *alert=[[UIAlertView alloc] initWithTitle:@"温馨提示" message:message delegate:nil
                                                cancelButtonTitle:@"确定" otherButtonTitles:nil];
            alert.alertViewStyle=UIAlertViewStyleDefault;
            [alert show];
            return;
            
        } else if (dataAsset.mediaType == PHAssetMediaTypeVideo) {//音频
            NSString *message = [NSString stringWithFormat:@"不能识别音频，请重新选择"];
            UIAlertView *alert=[[UIAlertView alloc] initWithTitle:@"温馨提示" message:message delegate:nil
                                                cancelButtonTitle:@"确定" otherButtonTitles:nil];
            alert.alertViewStyle=UIAlertViewStyleDefault;
            [alert show];
            return;
            
        } else if (dataAsset.mediaType == PHAssetMediaTypeUnknown) {//未知类型
            NSString *message = [NSString stringWithFormat:@"不是有效的图片，无法识别"];
            UIAlertView *alert=[[UIAlertView alloc] initWithTitle:@"温馨提示" message:message delegate:nil
                                                cancelButtonTitle:@"确定" otherButtonTitles:nil];
            alert.alertViewStyle=UIAlertViewStyleDefault;
            [alert show];
            return;
        }
    }
}

- (void)assetsPickerControllerDidCancel:(CTAssetsPickerController *)picker
{
    [picker dismissViewControllerAnimated:YES completion:nil];
}

- (BOOL)assetsPickerController:(CTAssetsPickerController *)picker shouldSelectAsset:(PHAsset *)asset
{
    // Allow 1 assets to be picked
    return (picker.selectedAssets.count < 1);
}

@end
